package com.liuya.safe.util;

import com.liuya.common.SpringUtils;
import com.liuya.safe.client.service.ApplicationManager;
import com.liuya.safe.client.service.UserTypeManager;
import com.liuya.safe.entitle.service.EntitleManagerService;
import com.liuya.safe.entitle.service.PrivilegeManagerService;
import com.liuya.safe.policy.service.QueryManagerService;
import com.liuya.safe.policy.service.UserCategoryManagerService;
import com.liuya.safe.system.role.service.impl.RoleManagerServiceImpl;
import com.liuya.safe.user.service.UserRoleManagerService;

import java.util.Iterator;
import java.util.Map;

public class Factory {
    private static java.util.Map privilegeManagers = new java.util.HashMap();
    private static java.util.Map roleManagers = new java.util.HashMap();
    private static java.util.Map userRoleManagers = new java.util.HashMap();
//    private static final ApplicationManager applicationManager;
//    private static final BackupManager backupManager;
//    private static final UserTypeManager userTypeManager;
    private static java.util.Map userManagers = new java.util.HashMap();
    private static java.util.Map filterManagers = new java.util.HashMap();
    private static java.util.Map queryManagers = new java.util.HashMap();
    private static java.util.Map userCategoryManagers = new java.util.HashMap();
    private static java.util.Map businessDataManagers = new java.util.HashMap();
    private static java.util.Map entitlementManagers = new java.util.HashMap();

    static {
//        applicationManager = new ApplicationManagerImpl();
//        userTypeManager = new UserTypeManagerImpl();
//        backupManager = new BackupManagerImpl();
    }

//    public static BackupManager getBackupManager() {
//        return backupManager;
//    }

    public static UserTypeManager getUserTypeManager() {
//        return userTypeManager;
        return (UserTypeManager) SpringUtils.getBean("userTypeManager");
    }

//    public static UserManager getUserManager(String userTypeName) {
//        if (userManagers.get(userTypeName) == null) {
//            UserType userType = Factory.getUserTypeManager().getUserType(userTypeName);
//            if (userType != null) {
//                UserManager userManager = new UserManager(userType);
//                userManagers.put(userTypeName, userManager);
//            }
//        }
//        return (UserManager) userManagers.get(userTypeName);
//    }

    /**
     * Update other managers when application changed.
     *
     * @param appName
     */
    public static synchronized void applicationChanged(String appName) {
        privilegeManagers.remove(appName);
        roleManagers.remove(appName);
        userRoleManagers.remove(appName);
        // commonElementManagers.remove( commonElementManagers.get( appName ) );
        // tableElementManagers.remove( tableElementManagers.get( appName ) );
        filterManagers.remove(appName);
        queryManagers.remove(appName);
        userCategoryManagers.remove(appName);
        businessDataManagers.remove(appName);
        entitlementManagers.remove(appName);
    }

    public static ApplicationManager getApplicationManager() {
//        return applicationManager;
        return (ApplicationManager) SpringUtils.getBean("applicationManager");
    }

    public static PrivilegeManagerService getPrivilegeManager(String appName) {
//        if (privilegeManagers.get(appName) == null) {
//            synchronized (privilegeManagers) {
//                privilegeManagers.put(appName, new PrivilegeManagerServiceImpl(appName));
//            }
//        }
//        return (PrivilegeManagerService) privilegeManagers.get(appName);

        return (PrivilegeManagerService) SpringUtils.getBean("privilegeManagerService");
    }

    public static synchronized RoleManagerServiceImpl getRoleManager(String appName) {
//        if (roleManagers.get(appName) == null) {
//            synchronized (roleManagers) {
//                roleManagers.put(appName, new RoleManagerImpl(appName));
//            }
//        }
//        return (RoleManager) roleManagers.get(appName);
        return (RoleManagerServiceImpl) SpringUtils.getBean("roleManagerService");
    }

    public static synchronized QueryManagerService getQueryManager(String appName) {
        return getQueryManager(appName, "queryManagerService");
    }

    public static synchronized QueryManagerService getQueryManager(String appName, String beanId) {
//        if (queryManagers.get(appName) == null) {
//            synchronized (queryManagers) {
//                queryManagers.put(appName, new QueryManagerServiceImpl(appName));
//            }
//        }
//        return (QueryManagerService) queryManagers.get(appName);
        return (QueryManagerService) SpringUtils.getBean(beanId);
    }

    public static synchronized UserCategoryManagerService getUserCategoryManager(String appName) {
//        if (userCategoryManagers.get(appName) == null) {
//            synchronized (userCategoryManagers) {
//                userCategoryManagers.put(appName, new UserCategoryManagerImpl(appName));
//            }
//        }
//        return (UserCategoryManager) userCategoryManagers.get(appName);
        return (UserCategoryManagerService) SpringUtils.getBean("userCategoryManagerService");
    }

//    public static synchronized BusinessDataManager getBusinessDataManager(String appName) {
//        if (businessDataManagers.get(appName) == null) {
//            synchronized (businessDataManagers) {
//                businessDataManagers.put(appName, new BusinessDataManagerImpl(appName));
//            }
//        }
//        return (BusinessDataManager) businessDataManagers.get(appName);
//    }

    public static synchronized EntitleManagerService getEntitleManager(String appName) {
        return getEntitleManager(appName, "entitleManagerService");
    }

    public static synchronized EntitleManagerService getEntitleManager(String appName, String beanId) {
//        if (entitlementManagers.get(appName) == null) {
//            synchronized (entitlementManagers) {
//                entitlementManagers.put(appName, new EntitleManagerImpl(appName));
//            }
//        }
//        return (EntitleManager) entitlementManagers.get(appName);
        Object bean = SpringUtils.getBean(beanId);
        if(bean!=null)
            return (EntitleManagerService) SpringUtils.getBean(beanId);
        return null;
    }

    public static synchronized UserRoleManagerService getUserRoleManager(String appName) {
        return getUserRoleManager(null, "userRoleManagerService");
    }

    public static synchronized UserRoleManagerService getUserRoleManager(String appName, String userTypeName) {
//        if (userRoleManagers.get(appName) == null) {
//            synchronized (userRoleManagers) {
//                userRoleManagers.put(appName, new java.util.HashMap());
//            }
//        }
//        Map userRoleManagerMap = (Map) userRoleManagers.get(appName);
//        if (userRoleManagerMap.get(userTypeName) == null) {
//            synchronized (userRoleManagerMap) {
//                userRoleManagerMap.put(userTypeName, new UserRoleManagerImpl(appName, userTypeName));
//            }
//        }
//        return (UserRoleManager) ((Map) userRoleManagers.get(appName)).get(userTypeName);
        return (UserRoleManagerService) SpringUtils.getBean(userTypeName);
    }

    /**
     * Update other managers when userType changed.
     *
     * @param userTypeName
     */
    public static synchronized void userTypeChanged(String userTypeName) {
        Iterator itr = userRoleManagers.values().iterator();
        while (itr.hasNext()) {
            Map userRoleManagerMap = (Map) itr.next();
            userRoleManagerMap.remove(userTypeName);
        }
    }

    /**
     * Update other managers when applicationUserType changed.
     *
     * @param appName
     */
    public static synchronized void applicationUserTypeChanged(String appName, String userTypeName) {
        Map userRoleManagerMap = (Map) userRoleManagers.get(appName);
        if (userRoleManagerMap != null) {
            userRoleManagerMap.remove(userTypeName);
        }
    }

}
